using System.Threading.Tasks;
using HslCommunication.BasicFramework;
using HslCommunication.Core;
using HslCommunication.Serial;

namespace HslCommunication.Profinet.LSIS
{
	/// <summary>
	/// XGB Cnet I/F module supports Serial Port.
	/// </summary>
	/// <remarks>
	/// <inheritdoc cref="T:HslCommunication.Profinet.LSIS.XGBCnetOverTcp" path="remarks" />
	/// </remarks>
	public class XGBCnet : SerialDeviceBase
	{
		/// <inheritdoc cref="P:HslCommunication.Profinet.LSIS.XGBCnetOverTcp.Station" />
		public byte Station
		{
			get;
			set;
		} = 5;


		/// <summary>
		/// Instantiate a Default object
		/// </summary>
		public XGBCnet()
		{
			base.ByteTransform = new RegularByteTransform();
			base.WordLength = 2;
		}

		/// <inheritdoc cref="M:HslCommunication.Profinet.LSIS.XGBCnetOverTcp.ReadByte(System.String)" />
		public OperateResult<byte> ReadByte(string address)
		{
			return ByteTransformHelper.GetResultFromArray(Read(address, 2));
		}

		/// <inheritdoc cref="M:HslCommunication.Profinet.LSIS.XGBCnetOverTcp.Write(System.String,System.Byte)" />
		public OperateResult Write(string address, byte value)
		{
			return Write(address, new byte[1]
			{
				value
			});
		}

		/// <inheritdoc />
		public override OperateResult<bool[]> ReadBool(string address, ushort length)
		{
			OperateResult<byte[]> operateResult = XGBCnetOverTcp.BuildReadOneCommand(Station, address, length);
			if (!operateResult.IsSuccess)
			{
				return OperateResult.CreateFailedResult<bool[]>(operateResult);
			}
			OperateResult<byte[]> operateResult2 = ReadBase(operateResult.Content);
			if (!operateResult2.IsSuccess)
			{
				return OperateResult.CreateFailedResult<bool[]>(operateResult2);
			}
			return OperateResult.CreateSuccessResult(SoftBasic.ByteToBoolArray(XGBCnetOverTcp.ExtractActualData(operateResult2.Content, isRead: true).Content, length));
		}

		/// <inheritdoc cref="M:HslCommunication.Profinet.LSIS.XGBCnetOverTcp.ReadCoil(System.String)" />
		public OperateResult<bool> ReadCoil(string address)
		{
			return ReadBool(address);
		}

		/// <inheritdoc cref="M:HslCommunication.Profinet.LSIS.XGBCnetOverTcp.ReadCoil(System.String,System.UInt16)" />
		public OperateResult<bool[]> ReadCoil(string address, ushort length)
		{
			return ReadBool(address, length);
		}

		/// <inheritdoc cref="M:HslCommunication.Profinet.LSIS.XGBCnet.WriteCoil(System.String,System.Boolean)" />
		public OperateResult WriteCoil(string address, bool value)
		{
			return Write(address, value);
		}

		/// <inheritdoc />
		public override OperateResult Write(string address, bool value)
		{
			return Write(address, new byte[1]
			{
				(byte)(value ? 1u : 0u)
			});
		}

		/// <inheritdoc />
		public override async Task<OperateResult> WriteAsync(string address, bool value)
		{
			return await WriteAsync(address, new byte[1]
			{
				(byte)(value ? 1u : 0u)
			});
		}

		/// <inheritdoc />
		public override OperateResult<byte[]> Read(string address, ushort length)
		{
			OperateResult<byte[]> operateResult = XGBCnetOverTcp.BuildReadCommand(Station, address, length);
			if (!operateResult.IsSuccess)
			{
				return operateResult;
			}
			OperateResult<byte[]> operateResult2 = ReadBase(operateResult.Content);
			if (!operateResult2.IsSuccess)
			{
				return operateResult2;
			}
			return XGBCnetOverTcp.ExtractActualData(operateResult2.Content, isRead: true);
		}

		/// <inheritdoc />
		public override OperateResult Write(string address, byte[] value)
		{
			OperateResult<byte[]> operateResult = XGBCnetOverTcp.BuildWriteCommand(Station, address, value);
			if (!operateResult.IsSuccess)
			{
				return operateResult;
			}
			OperateResult<byte[]> operateResult2 = ReadBase(operateResult.Content);
			if (!operateResult2.IsSuccess)
			{
				return operateResult2;
			}
			return XGBCnetOverTcp.ExtractActualData(operateResult2.Content, isRead: false);
		}

		/// <inheritdoc />
		public override string ToString()
		{
			return $"XGBCnet[{base.PortName}:{base.BaudRate}]";
		}
	}
}
